#coding:utf-8
import tensorflow as tf
import glob
import os.path
import numpy as np
from tensorflow.python.platform import gfile

INPUT_DATA = 'D:/TSBrowserDownloads/201806-github代码数据打包/datasets/flower_photos/'
OUTPUT_FILE = 'E:/flower/flower_processed_data.npy' #输出图片用numpy格式保存

#测试数据和验证数据比例
VALIDATION_PERCENTAGE = 10
TEST_PERCENTAGE = 10

#读出数据，并将数据分为验证、测试、训练数据
def create_image_lists(sess,testing_percentage,validatation_percentage):
    sub_dirs = [x[0] for x in os.walk(INPUT_DATA)] #os.walk() 方法用于通过在目录树中游走输出在目录中的文件名，向上或者向下
    is_root_dir = True

    #初始化各个数据集
    training_images = []
    training_labels = []
    testing_images = []
    testing_labels = []
    validation_images = []
    validation_labels = []
    current_label = 0
    list = []
    #读取所有子目录
    for sub_dir in sub_dirs:
        if is_root_dir:
            is_root_dir = False
            continue
        #获取一个子目录中所有的图片文件
        #由于windows系统下，文件名不区分大小写，所以应写作：
        extensions = ['jpg','jpeg']
        file_list = []
        dir_name = os.path.basename(sub_dir)#用到os.path.basename(),返回path最后的文件名。若path以/或\结尾，那么就会返回空值。
        for extension in extensions:
            file_glob = os.path.join(INPUT_DATA,dir_name,'*.'+extension) #将路径名整合到一起
            # extend将多个列表整合在一起，glob.glob函数匹配所有的符合条件的文件，并将其以list的形式返回,
            # 相当于通配符 daisy文件夹大约有633张JPG图片
            file_list.extend(glob.glob(file_glob))
        if not file_list:continue
        print("processing:", dir_name,"-",len(file_list))
        i = 0
        #处理图片数据
        for file_name in file_list:
            i = i+1
            #读取并解析图片，将图片转化成299*299
            image_raw_data = gfile.FastGFile(file_name,'rb').read()
            image = tf.image.decode_jpeg(image_raw_data)
            if image.dtype != tf.float32:
                image = tf.image.convert_image_dtype(image,dtype=tf.float32)
            image = tf.image.resize_images(image,[299,299])
            image_value = sess.run(image)
            # #随机化分数据集
            # chance = np.random.randint(100)
            # if chance < validatation_percentage:
            #     validation_images.append(image_value)
            #     validation_labels.append(current_label)
            # elif chance < (testing_percentage + validatation_percentage):
            #     testing_images.append(image_value)
            #     testing_labels.append(current_label)
            # else:
            #     training_images.append(image_value)
            #     training_labels.append(current_label)
            # if i % 200 == 0:
            #     print(i, "images processed.")
        current_label += 1

    #将训练数据随机打乱已获得更好的训练效果

    #功能：获取随机生成器 np.random的状态
    #作用：常与np.random.set_state() 搭配使用。使随机生成器random保持相同的状态（state）
    # 通过设置相同的state,使得random.shuffle以相同的规律打乱两个列表，进而使得两个列表被打乱后，
    # 仍旧能维持两个列表间元素的一一对应关系。这一点在深度学习的标注数据集的打乱的过程中很有用。
    # state = np.random.get_state()
    # np.random.shuffle(training_images)
    # np.random.set_state(state)
    # np.random.shuffle(training_labels)
    #array和asarray都可将结构数据转换为ndarray类型。
   # return np.asarray([training_images,training_labels,
   #                     validation_images,validation_labels,
   #                     testing_images,testing_labels])
    # return 0
    return np.asarray([training_images,training_labels])
#数据整理函数
def main():
    with tf.Session() as sess:
        processed_data = create_image_lists(sess,TEST_PERCENTAGE,VALIDATION_PERCENTAGE)
        #通过numpy格式保存处理后的数据
        np.save(OUTPUT_FILE,processed_data)

if __name__ == '__main__':
    main()